/*
* 记忆函数：
*   接收一个函数，并且把这个函数改造成可以缓存数据的一个函数
*
* */
function memorize(fn){
    //用一个闭包来存储缓存结果
    let cache = {} //存储缓存数据的结构，通过key来查找value。key（键）是fn参数所组成的，value（值）就是在某个参数下的执行结果
    return function (){
        let key = arguments.length + Array.prototype.join.call(arguments,",")
        console.log(key)
        if(key in cache){ //如果存在值
            return cache[key]
        }else{
            return cache[key] = fn.apply(this,arguments)
        }
    }
}

function factorial(n){

    //递归方法必须有一个出口
    if(n === 1 || n === 0){ //出口，满足什么条件就跳出递归
        return 1
    }

    //递归还需要一个入口
    return n * fn(n-1) //满足什么条件就进入递归
}

let fn = memorize(factorial)

fn(10)
fn(11)